package com.kotlin.coroutine.to_use.domain

import kotlinx.coroutines.*
import org.springframework.stereotype.Service

@Service
class RunBlockingService {

    fun test(){
        /***
         * runBlocking可以理解为一个锁块儿，内部的普通方法和代码都是同步执行的。
         * 可以将协程代码写入runBlocking内部执行，这样外部方法无需添加suspend即可执行。
         */
        return runBlocking {
            query1()
            query2()

            async {
                doWorld()
            }
            println("Hello")
        }
    }

    /***
     * suspend修饰的方法，可以被放在任何协程的高阶函数中被调用。
     * 如： runBlocking、 lunch、 async、 withContext
     */
    suspend fun doWorld() {
        delay(1000L)
        println("World!")
    }

    // 单纯的withContext无法直接产生异步的效果。 可通过以下的query1 query2进行验证
    suspend fun query1(){
        withContext(Dispatchers.Default) {  // 👈 切换到 IO 线程，并在执行完成后切回 UI 线程
            var i = 0
            while (true){
                println(i++)
                if(i>10) break
            }
            delay(1000)
        }
    }
    suspend fun query2(){
        withContext(Dispatchers.IO) {  // 👈 切换到 IO 线程，并在执行完成后切回 UI 线程
            var i = 0
            while (true){
                println(i++)
                if(i>10) break
            }
            delay(1000)
        }
    }

}